package cln.gui.com;

import org.w3c.dom.Document;
import org.w3c.dom.Element;
import org.w3c.dom.Node;
import org.xml.sax.Attributes;
import org.xml.sax.SAXException;
import org.xml.sax.helpers.DefaultHandler;

import javax.xml.parsers.ParserConfigurationException;
import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;

class DocumentFragmentInserter 
{
  protected final SAXParser m_Parser;
  protected Document m_Document;
  protected Node m_InsertNode;
  protected Handler m_DocumentHandler;

  public DocumentFragmentInserter()
  throws SAXException, ParserConfigurationException 
  {
    this(SAXParserFactory.newInstance().newSAXParser());
  }//DocumentFragmentInserter

  public DocumentFragmentInserter(SAXParser parser) 
  {
    this.m_Parser = parser;
  }//DocumentFragementBuilder

  /**
   * Treats the xml parameter as a well-formed XML document to be inserted
   * into the given document.
   */
  public void parse(Document doc, Node insert, String xml)
  throws SAXException 
  {
    try 
    {
      parse(doc, insert, new ByteArrayInputStream(xml.getBytes("UTF-8")));
    }
    catch (IOException ex) {}
  }//parse

  /**
   * Treats the xml parameter as a well-formed XML document to be inserted
   * into m_Document.
   */
  public void parse(Document doc, Node insert, InputStream xml)
  throws SAXException, IOException 
  {
    m_Document = doc;
    m_InsertNode = insert;

    m_Parser.parse(xml, getDocumentHandler());
  }//parse

  protected DefaultHandler getDocumentHandler() 
  {
    if (m_DocumentHandler == null) 
    {
      m_DocumentHandler = new Handler();
    }
    
    return m_DocumentHandler;
  }//getDocumentHandler

  protected class Handler extends DefaultHandler 
  {

    protected Node m_Current = m_InsertNode;

    public void characters(char [] ch, int start, int length) 
    {
      m_Current.appendChild( m_Document.createTextNode( new String( ch, start, length ) ) );
    }//characters

    public void endElement(String uri, String localName, String qName)
    throws SAXException 
    {
      m_Current = m_Current.getParentNode();
    }//endElement

    public void processingInstruction(String target, String data) 
    {
      m_Current.appendChild( m_Document.createProcessingInstruction( target, data ) );
    }//processingInstruction

    public void startElement(String uri, String localName, String qName, Attributes attributes)
        throws SAXException 
    {
      //System.out.println(qName);
      Element e = m_Document.createElement( qName );
      m_Current.appendChild( e );
      m_Current = e;
      int nAtts = attributes.getLength();
      for (int i = 0; i < nAtts; i++) 
      {
        String qn = attributes.getQName(i);
        String val = attributes.getValue(i);
        e.setAttribute(qn, val);
        if("id".equals(qn)) 
        {
          e.setIdAttribute(qn,true);
        }
      }
    }//startElement

  }//class Handler

}//DocumentFragmentInserter
